package com.atguigu.gmall.order.service.impl;

import com.atguigu.gmall.common.constant.MqConst;
import com.atguigu.gmall.common.constant.RedisConst;
import com.atguigu.gmall.common.service.RabbitService;
import com.atguigu.gmall.common.util.HttpClientUtil;
import com.atguigu.gmall.model.cart.CartInfo;
import com.atguigu.gmall.model.enums.OrderStatus;
import com.atguigu.gmall.model.enums.PaymentWay;
import com.atguigu.gmall.model.enums.ProcessStatus;
import com.atguigu.gmall.model.order.OrderDetail;
import com.atguigu.gmall.model.order.OrderInfo;
import com.atguigu.gmall.order.mapper.OrderDetailMapper;
import com.atguigu.gmall.order.mapper.OrderInfoMapper;
import com.atguigu.gmall.order.service.OrderService;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.BoundHashOperations;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;

@Service
@SuppressWarnings("all")
public class OrderServiceImpl extends ServiceImpl<OrderInfoMapper,OrderInfo> implements OrderService {


    @Autowired
    private OrderInfoMapper orderInfoMapper;

    @Autowired
    private OrderDetailMapper orderDetailMapper;

    @Autowired
    private RedisTemplate redisTemplate;
    @Autowired
    private RabbitService rabbitService;

    @Value("${ware.url}")
    private  String wareUrl;

    /**
     * 提交订单
     * @param orderInfo
     * @return
     *
     * 涉及到的表：
     *  order_info 订单表
     *  order_detail 订单明细表
     *  关系：一对多  外键：order_id
     *
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Long submitOrder(OrderInfo orderInfo) {

        //计算总金额
        orderInfo.sumTotalAmount();
        //订单状态
        orderInfo.setOrderStatus(OrderStatus.UNPAID.name());
        //订单交易编号
        String outTradeNo="ATGUIGU"+System.currentTimeMillis()+""+ new Random().nextInt(1000);
       orderInfo.setOutTradeNo(outTradeNo);
       //获取商品详情
        List<OrderDetail> orderDetailList = orderInfo.getOrderDetailList();
        StringBuilder tradeBody=new StringBuilder();
        for (OrderDetail orderDetail : orderDetailList) {
            tradeBody.append(orderDetail.getSkuName()).append("  ");

        }
        //判断长度
        if(tradeBody.toString().length()>100){

            orderInfo.setTradeBody(tradeBody.toString().substring(0,100));
        }else{
            orderInfo.setTradeBody(tradeBody.toString());

        }
        //操作时间
        orderInfo.setOperateTime(new Date());
        //失效时间 -1天
        Calendar calendar = Calendar.getInstance();
        calendar.add(Calendar.DATE,1);
        Date time = calendar.getTime();
        orderInfo.setExpireTime(time);
        //进度状态
        orderInfo.setProcessStatus(ProcessStatus.UNPAID.name());

        //支付方式
        orderInfo.setPaymentWay(PaymentWay.ONLINE.name());

         //执行保存
        orderInfoMapper.insert(orderInfo);

        //购物车怎么办？--删除已经生成订单
//        BoundHashOperations<String,String, CartInfo> boundHashOps = redisTemplate.boundHashOps(RedisConst.USER_KEY_PREFIX + orderInfo.getUserId() + RedisConst.USER_CART_KEY_SUFFIX);

        //保存订单明细
        for (OrderDetail orderDetail : orderDetailList) {

            //设置关联字段orderId
            orderDetail.setOrderId(orderInfo.getId());
            //保存
            orderDetailMapper.insert(orderDetail);

//            boundHashOps.delete(orderDetail.getSkuId().toString());
        }

        //发送延迟消息
         rabbitService.sendDelayedMessage(
                 MqConst.EXCHANGE_DIRECT_ORDER_CANCEL,
                 MqConst.ROUTING_ORDER_CANCEL,orderInfo.getId(),MqConst.DELAY_TIME);


        return orderInfo.getId();
    }

    /**
     * 生成流水号
     * @param userId
     * @return
     */
    @Override
    public String getTradeNo(String userId) {
        //生成流水号
        String tradeNo = UUID.randomUUID().toString().replaceAll("-", "");

        // 定义key
        String tradeNoKey = "user:" + userId + ":tradeCode";
        //存储到redis
        redisTemplate.opsForValue().set(tradeNoKey,tradeNo);

        return tradeNo;
    }

    /**
     * 校验流水号
     * @param userId
     * @param tradeCodeNo
     * @return
     */
    @Override
    public boolean checkTradeCode(String userId, String tradeCodeNo) {
        // 定义key
        String tradeNoKey = "user:" + userId + ":tradeCode";
        //获取redis中流水号
        String redisTradeNo = (String) redisTemplate.opsForValue().get(tradeNoKey);


        return tradeCodeNo.equals(redisTradeNo);
    }

    @Override
    public void deleteTradeNo(String userId) {
// 定义key
        String tradeNoKey = "user:" + userId + ":tradeCode";
        redisTemplate.delete(tradeNoKey);

    }

    @Override
    public boolean chechStock(Long skuId, Integer skuNum) {

        //请求路径 http://localhost:9001/hasStock?skuId=21&num=51

        String result = HttpClientUtil.doGet(wareUrl+"/hasStock?skuId=" + skuId + "&num=" + skuNum);

        return "1".equals(result);
    }

    @Override
    public IPage<OrderInfo> getOrderPageList(Page<OrderInfo> orderInfoPage, String userId) {

      IPage<OrderInfo> infoIPage=orderInfoMapper.selectOrderPageList(orderInfoPage,userId);

        List<OrderInfo> records = infoIPage.getRecords();
        records.stream().forEach(orderInfo -> {


            orderInfo.setOrderStatusName(OrderStatus.getStatusNameByStatus(orderInfo.getOrderStatus()));

        });


        return infoIPage;
    }

    /**
     * 关闭超时订单
     * @param orderId
     */
    @Override
    public void execExpireOrder(Long orderId) {
        this.updateOrderStatus(orderId,ProcessStatus.CLOSED);


    }

    @Override
    public void updateOrderStatus(Long orderId, ProcessStatus processStatus) {
        //创建对象
        OrderInfo orderInfo=new OrderInfo();
        //设置id
        orderInfo.setId(orderId);
        //设置修改的订单状态
        System.out.println(processStatus.getOrderStatus().name());
        orderInfo.setOrderStatus(processStatus.getOrderStatus().name());
        //设置吸怪的订单进度状态
        orderInfo.setProcessStatus(processStatus.name());
        orderInfoMapper.updateById(orderInfo);
    }
}
